全局中间件之 CheckForMaintenanceMode
简介
上一章,我们看了 Pipeline 管道操作如何实现请求穿透中间件。从本章开始,我们将逐一介绍 Laravel 五大全局中间件对请求做了什么。。
做了什么:首先,应该要弄清如何做的,上一章我有提到过,就是以请求和洋葱作为参数,执行中间件的 handle 方法。
先看一下五大中间件有哪些
protected $middleware = [
\App\Http\Middleware\CheckForMaintenanceMode::class,
\Illuminate\Foundation\Http\Middleware\ValidatePostSize::class,
\App\Http\Middleware\TrimStrings::class,
\Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull::class,
\App\Http\Middleware\TrustProxies::class,
];
这一章,我们看一下第一个中间 App\Http\Middleware\CheckForMaintenanceMode
。
关于 App\Http\Middleware\CheckForMaintenanceMode
从字面意思不难看出,这个中间件是检测我们整个项目有没有处于 维护模式。
关于维护模式,下面是一段官方文档的说明:
https://learnku.com/docs/laravel/5.6/configuration/1353#972c4c
开启维护模式
php artisan down
这条命令做了什么呢?
这个要看
Illuminate\Foundation\Console\DownCommand
,此类就是php artisan down
所要运行的命令类<?php
namespace Illuminate\Foundation\Console;
use Illuminate\Console\Command;
use Illuminate\Support\InteractsWithTime;
class DownCommand extends Command
{
use InteractsWithTime;
/**
* 命令签名:就是执行 php artisan down 后面加的命令参数
*/
protected $signature = 'down {--message= : The message for the maintenance mode. }
{--retry= : The number of seconds after which the request may be retried.}
{--allow=* : IP or networks allowed to access the application while in maintenance mode.}';
/**
* down 命令的描述
*
* Put the application into maintenance mode : 意思是开启 Laravel 应用的维护模式
*/
protected $description = 'Put the application into maintenance mode';
/**
* 这个就是执行 php artisan down 命令实际运行的逻辑代码
*/
public function handle()
{
// 在 storage/framework/ 目录下写入 down 文件,格式是 getDownFilePayload 方法的返回。
file_put_contents(
storage_path('framework/down'),
json_encode($this->getDownFilePayload(), JSON_PRETTY_PRINT)
);
// 在屏幕打印成功的消息
$this->comment('Application is now in maintenance mode.');
}
/**
* down 文件的内容格式
*/
protected function getDownFilePayload()
{
return [
'time' => $this->currentTime(),
'message' => $this->option('message'),
'retry' => $this->getRetryTime(),
'allowed' => $this->option('allow'),
];
}
/**
* 获取浏览器刷新前应该等待的秒数。
*/
protected function getRetryTime()
{
$retry = $this->option('retry');
return is_numeric($retry) && $retry > 0 ? (int) $retry : null;
}
}通过 down 命令的源码我们不难看出,它的作用无非就是在
storage/framework/
目录下创建叫down
文件,里面的内容有:time
开启维护的时间message
页面的提示信息retry
浏览器每隔多长时间刷新一次allowed
允许进入应用的 IP 地址组
说百遍,道万千,不如一张图----->
关闭维护模式
php artisan up
简单,不就是删掉
down
文件吗。。。这个源码不需要看了吧,不需要看了吧,不回答,就是默认喽。。好,那就不看了。。
那么,我们开启维护模式了,Laravel 又是如何知道呢(好能噢~~~~)
这个就是
App\Http\Middleware\CheckForMaintenanceMode
中间件的作用了,它会知道我们到底有没有开维护模式。(好能噢~~~~)
看源码:
<?php
namespace App\Http\Middleware;
use Illuminate\Foundation\Http\Middleware\CheckForMaintenanceMode as Middleware;
class CheckForMaintenanceMode extends Middleware
{
/**
* 这里是定义 路由除外,意思是除了这些路由正常进入应用,其它路由过来甩它一脸。
*
* @var array
*/
protected $except = [
//
];
}
咦? handle 方法呢。。哦,原来这是子类,那肯定是在父类了,不废话了直接上父类的 handle 方法
public function handle($request, Closure $next)
{
// if 就是看有没有 down 文件;有则执行 if 里面的代码
if ($this->app->isDownForMaintenance()) {
// 将 down 文件里面的json数据转换成数组
$data = json_decode(file_get_contents($this->app->storagePath().'/framework/down'), true);
// 看一下数组里面的 allowed 与请求过来的 IP 匹配吗,匹配就进入应用
if (isset($data['allowed']) && IpUtils::checkIp($request->ip(), (array) $data['allowed'])) {
return $next($request);
}
// 这个就是看一下子类定义的除外路由,有没有与请求的路由匹配上,匹配上就进入应用
if ($this->inExceptArray($request)) {
return $next($request);
}
// 经过披荆斩棘,一路坎坷,没有一个符合条件,不好意思,甩你一脸狗粮(维护页面),难受不。。。哈哈哈
throw new MaintenanceModeException($data['time'], $data['retry'], $data['message']);
}
return $next($request);
}
代码里面说的很明白了,,再深了的内容,比如如何判断有米有 down 文件,就请各位小伙伴,自己走进去一探究竟了哈,我这里就不看了。